Micron Document
--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
| SparkN0de-git | SparkN0de |
--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------


Commit 0ae5f2bda55128261e22725815ffa67aa5b924fa


Parents : ec74a26
Author : Ivan <e46112d44649266d71fe2193e00a4710>
Signature : T66BB85Valid, signed by author
Date : 2026-07-19T14:13:35-05:00

feat: update API contract tests with new export request helper and update JSON formatting for route fixtures

Changes
Diff

diff --git a/meshchatx.rsm b/meshchatx.rsm
index 53531b3e..e3194aba 100644
Binary files a/meshchatx.rsm and b/meshchatx.rsm differ

diff --git a/tests/backend/fixtures/http_api_routes.json b/tests/backend/fixtures/http_api_routes.json
index 9c9ea6ba..be57e21e 100644
--- a/tests/backend/fixtures/http_api_routes.json
+++ b/tests/backend/fixtures/http_api_routes.json
@@ -300,6 +300,58 @@
"method": "POST",
"path": "/api/v1/favourites/{destination_hash}/rename"
},
+ {
+ "method": "GET",
+ "path": "/api/v1/filesync/acl"
+ },
+ {
+ "method": "POST",
+ "path": "/api/v1/filesync/acl"
+ },
+ {
+ "method": "POST",
+ "path": "/api/v1/filesync/announce"
+ },
+ {
+ "method": "POST",
+ "path": "/api/v1/filesync/browse"
+ },
+ {
+ "method": "POST",
+ "path": "/api/v1/filesync/connect"
+ },
+ {
+ "method": "POST",
+ "path": "/api/v1/filesync/disconnect"
+ },
+ {
+ "method": "POST",
+ "path": "/api/v1/filesync/download"
+ },
+ {
+ "method": "GET",
+ "path": "/api/v1/filesync/files"
+ },
+ {
+ "method": "GET",
+ "path": "/api/v1/filesync/peers"
+ },
+ {
+ "method": "PATCH",
+ "path": "/api/v1/filesync/settings"
+ },
+ {
+ "method": "POST",
+ "path": "/api/v1/filesync/start"
+ },
+ {
+ "method": "GET",
+ "path": "/api/v1/filesync/status"
+ },
+ {
+ "method": "POST",
+ "path": "/api/v1/filesync/stop"
+ },
{
"method": "GET",
"path": "/api/v1/gifs"
@@ -537,20 +589,16 @@
"path": "/api/v1/maintenance/messages"
},
{
- "method": "GET",
- "path": "/api/v1/maintenance/messages/export"
- },
- {
- "method": "GET",
+ "method": "DELETE",
"path": "/api/v1/maintenance/messages/duplicates"
},
{
- "method": "DELETE",
+ "method": "GET",
"path": "/api/v1/maintenance/messages/duplicates"
},
{
"method": "GET",
- "path": "/api/v1/maintenance/messages/purge-preview"
+ "path": "/api/v1/maintenance/messages/export"
},
{
"method": "POST",
@@ -560,6 +608,10 @@
"method": "POST",
"path": "/api/v1/maintenance/messages/import-file"
},
+ {
+ "method": "GET",
+ "path": "/api/v1/maintenance/messages/purge-preview"
+ },
{
"method": "DELETE",
"path": "/api/v1/maintenance/path-table"
@@ -1112,6 +1164,10 @@
"method": "POST",
"path": "/api/v1/rnx/sessions/{session_id}/stop"
},
+ {
+ "method": "POST",
+ "path": "/api/v1/rrc/active/clear"
+ },
{
"method": "GET",
"path": "/api/v1/rrc/hubs"
@@ -1172,10 +1228,6 @@
"method": "POST",
"path": "/api/v1/rrc/hubs/{hub_hash}/rooms/{room}/read"
},
- {
- "method": "POST",
- "path": "/api/v1/rrc/active/clear"
- },
{
"method": "GET",
"path": "/api/v1/rrc/servers"

diff --git a/tests/backend/http_api_contract_helpers.py b/tests/backend/http_api_contract_helpers.py
index 2ba77fd1..dbeebfa9 100644
--- a/tests/backend/http_api_contract_helpers.py
+++ b/tests/backend/http_api_contract_helpers.py
@@ -67,6 +67,6 @@ def load_route_fixture(fixture_path: Path) -> list[dict[str, str]]:
def write_route_fixture(fixture_path: Path, routes: list[dict[str, str]]) -> None:
fixture_path.parent.mkdir(parents=True, exist_ok=True)
fixture_path.write_text(
- json.dumps({"routes": routes}, indent=2) + "\n",
+ json.dumps({"routes": routes}, indent=4) + "\n",
encoding="utf-8",
)

diff --git a/tests/backend/test_messages_export.py b/tests/backend/test_messages_export.py
index 75226011..86eed8ce 100644
--- a/tests/backend/test_messages_export.py
+++ b/tests/backend/test_messages_export.py
@@ -21,6 +21,13 @@ def _make_json_request(body):
return request
+def _make_export_request(**query):
+ """GET export reads request.query. Bare MagicMock makes .get() truthy junk."""
+ request = MagicMock()
+ request.query = dict(query)
+ return request
+
+
def _make_multipart_file_request(body: bytes):
class _MultipartField:
name = "file"
@@ -165,7 +172,7 @@ async def test_messages_export_with_icons(mock_rns_minimal, temp_dir):
break
assert handler is not None
- request = MagicMock()
+ request = _make_export_request()
response = await handler(request)
data = json.loads(response.body)
assert "messages" in data
@@ -227,7 +234,7 @@ async def test_messages_export_without_icons(mock_rns_minimal, temp_dir):
break
assert handler is not None
- request = MagicMock()
+ request = _make_export_request()
response = await handler(request)
data = json.loads(response.body)
assert len(data["messages"]) == 1
@@ -283,7 +290,7 @@ async def test_messages_import_export_roundtrip(mock_rns_minimal, temp_dir):
assert export_handler is not None
assert import_handler is not None
- export_response = await export_handler(MagicMock())
+ export_response = await export_handler(_make_export_request())
export_data = json.loads(export_response.body)
assert len(export_data["messages"]) == 1
assert "lxmf_icon" not in export_data["messages"][0]

diff --git a/tests/backend/test_messages_export_bundle.py b/tests/backend/test_messages_export_bundle.py
index 92bad668..62a02c04 100644
--- a/tests/backend/test_messages_export_bundle.py
+++ b/tests/backend/test_messages_export_bundle.py
@@ -26,6 +26,13 @@ def _make_json_request(body):
return request
+def _make_export_request(**query):
+ """GET export reads request.query. Bare MagicMock makes .get() truthy junk."""
+ request = MagicMock()
+ request.query = dict(query)
+ return request
+
+
@pytest.fixture
def temp_dir():
dir_path = tempfile.mkdtemp()
@@ -111,7 +118,7 @@ async def test_messages_export_includes_contacts_names_and_read_state(
handler = route.handler
break
assert handler is not None
- response = await handler(MagicMock())
+ response = await handler(_make_export_request())
data = json.loads(response.body)
assert data["format"] == MESSAGE_EXPORT_FORMAT

diff --git a/tests/backend/test_telephone_audio_ws.py b/tests/backend/test_telephone_audio_ws.py
index 3444939d..54d2f5ab 100644
--- a/tests/backend/test_telephone_audio_ws.py
+++ b/tests/backend/test_telephone_audio_ws.py
@@ -27,7 +27,12 @@ def web_audio_app(mock_app):
@pytest.mark.asyncio
-async def test_telephone_audio_ws_disabled_config_returns_error(web_audio_app):
+async def test_telephone_audio_ws_disabled_config_returns_error(
+ web_audio_app,
+ monkeypatch,
+):
+ monkeypatch.setattr(web_audio_app, "web_audio_required", lambda: False)
+
bridge = MagicMock()
bridge.config_enabled.return_value = False
bridge.send_status = AsyncMock()


──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────